package com.xgk.boot.module.core.service.product;

import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.mzt.logapi.context.LogRecordContext;
import com.mzt.logapi.starter.annotation.LogRecord;
import com.xgk.boot.framework.common.pojo.PageParam;
import com.xgk.boot.framework.common.pojo.PageResult;
import com.xgk.boot.framework.common.util.object.BeanUtils;
import com.xgk.boot.framework.mybatis.core.query.LambdaQueryWrapperX;
import com.xgk.boot.module.core.controller.admin.customer.vo.CustomerReqVO;
import com.xgk.boot.module.core.controller.admin.customer.vo.CustomerVO;
import com.xgk.boot.module.core.controller.admin.product.vo.product.*;
import com.xgk.boot.module.core.dal.dto.CustomerProductDto;
import com.xgk.boot.module.core.dal.entity.customer.CustomerDO;
import com.xgk.boot.module.core.dal.entity.product.ProductCustomerDO;
import com.xgk.boot.module.core.dal.entity.product.ProductDO;
import com.xgk.boot.module.core.dal.entity.product.ProductPriceRuleDO;
import com.xgk.boot.module.core.dal.iservice.CustomerService;
import com.xgk.boot.module.core.dal.iservice.ProductCustomerService;
import com.xgk.boot.module.core.dal.iservice.ProductPriceRuleService;
import com.xgk.boot.module.core.dal.iservice.ProductService;
import com.xgk.boot.module.core.dal.mapper.product.ProductCustomerMapper;
import com.xgk.boot.module.core.dal.mapper.product.ProductPriceRuleMapper;
import com.xgk.boot.module.core.service.customer.CustomerServiceImpl;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;

import static com.xgk.boot.module.core.enums.LogRecordConstants.*;

@Slf4j
@Service
public class ProductCustomerServiceImpl extends ServiceImpl<ProductCustomerMapper, ProductCustomerDO> implements ProductCustomerService {

    @Resource
    private ProductServiceImpl productService;

    @Resource
    private CustomerServiceImpl customerService;


    public PageResult<CustomerProductVO> pageListByCustomer(ProductDistbuteReqVO productDistbuteReqVO){
        CustomerReqVO customerReqVO = new CustomerReqVO();
        customerReqVO.setLikeName(productDistbuteReqVO.getCustomerName());
        customerReqVO.setLikeCode(productDistbuteReqVO.getCustomerCode());
        customerReqVO.setStatus(productDistbuteReqVO.getCustomerStatus());
        customerReqVO.setCurrent(productDistbuteReqVO.getCurrent());
        customerReqVO.setPageSize(productDistbuteReqVO.getPageSize());
        PageResult<CustomerDO> pageData = customerService.pageCustomers(customerReqVO);
        List<CustomerDO> data = pageData.getData();
        if(CollUtil.isEmpty(data)){
            return new PageResult<>();
        }
        List<CustomerProductVO> customerProductVOS = BeanUtils.toBean(data, CustomerProductVO.class);

        Set<Long> customerIds = customerProductVOS.stream().map(CustomerProductVO::getId).collect(Collectors.toSet());
        List<CustomerProductDto> list = this.baseMapper.listByCustomerIds(customerIds);
        if(CollUtil.isNotEmpty(list)){
            Map<Long, List<CustomerProductDto>> map = list.stream().collect(Collectors.groupingBy(CustomerProductDto::getId));
            for (CustomerProductVO customerProductVO : customerProductVOS) {
                customerProductVO.setProducts(map.get(customerProductVO.getId()));
            }
        }
        return new PageResult<CustomerProductVO>(customerProductVOS,pageData.getTotal(),productDistbuteReqVO.getCurrent(),productDistbuteReqVO.getPageSize());
    }

    public PageResult<ProductCustomerVO> pageListByProduct(ProductDistbuteReqVO productDistbuteReqVO){
        ProductPageReqVO productPage = new ProductPageReqVO();
        productPage.setPrName(productDistbuteReqVO.getPrName());
        productPage.setPrCode(productDistbuteReqVO.getPrCode());
        productPage.setPrStatus(productDistbuteReqVO.getPrStatus());
        productPage.setCurrent(productDistbuteReqVO.getCurrent());
        productPage.setPageSize(productDistbuteReqVO.getPageSize());
        PageResult<ProductDO> pageData = productService.getBaseMapper().selectPage(productPage);
        List<ProductDO> data = pageData.getData();
        if(CollUtil.isEmpty(data)){
            return new PageResult<>();
        }
        List<ProductCustomerVO> productCustomerVOS = BeanUtils.toBean(data, ProductCustomerVO.class);

        Set<Long> productIds = productCustomerVOS.stream().map(ProductCustomerVO::getPrId).collect(Collectors.toSet());
        List<CustomerProductDto> list = this.baseMapper.listByProductIds(productIds);
        if(CollUtil.isNotEmpty(list)){
            Map<Long, List<CustomerProductDto>> map = list.stream().collect(Collectors.groupingBy(CustomerProductDto::getPrId));
            for (ProductCustomerVO productCustomerVO : productCustomerVOS) {
                productCustomerVO.setCustomers(map.get(productCustomerVO.getPrId()));
            }
        }
        return new PageResult<ProductCustomerVO>(productCustomerVOS,pageData.getTotal(),productDistbuteReqVO.getCurrent(),productDistbuteReqVO.getPageSize());
    }

    @Transactional(rollbackFor = Exception.class)
    @LogRecord(type = SYSTEM_PRODUCT_TYPE, subType = SYSTEM_PRODUCT_CUSTOMER_TYPE, bizNo = "{{#productId}}", success = SYSTEM_PRODUCT_CUSTOMER_SUCCESS)
    public boolean updateProductCustomer(Long productId, List<CustomerVO> customerVOList){
        ProductDO byId = productService.getById(productId);
        if(byId ==null){
            return false;
        }
        LogRecordContext.putVariable("product", byId);
        LambdaQueryWrapperX<ProductCustomerDO> eq = new LambdaQueryWrapperX<ProductCustomerDO>().eq(ProductCustomerDO::getProductId, productId);
        this.remove(eq);
        if(CollUtil.isEmpty(customerVOList)){
            return true;
        }
        List<ProductCustomerDO> list = new ArrayList<>();
        for (CustomerVO customerVO : customerVOList) {
            ProductCustomerDO pcDo = new ProductCustomerDO();
            pcDo.setCustomerId(customerVO.getId());
            pcDo.setCustomerCode(customerVO.getCustomerCode());
            pcDo.setProductId(byId.getPrId());
            pcDo.setProductCode(byId.getPrCode());
            list.add(pcDo);
        }

        return  this.saveBatch(list);
    }

    @Transactional(rollbackFor = Exception.class)
    @LogRecord(type = SYSTEM_PRODUCT_TYPE, subType = SYSTEM_PRODUCT_CUSTOMER_TYPE, bizNo = "{{#customerId}}", success = SYSTEM_CUSTOMER_PRODUCT_SUCCESS)
    public boolean updateCustomerProduct(Long customerId, List<ProductInfoVO> productInfoVOList){
        CustomerDO byId = customerService.getById(customerId);
        if(byId ==null){
            return false;
        }
        LogRecordContext.putVariable("customer", byId);
        LambdaQueryWrapperX<ProductCustomerDO> eq = new LambdaQueryWrapperX<ProductCustomerDO>().eq(ProductCustomerDO::getCustomerId, customerId);
        this.remove(eq);
        if(CollUtil.isEmpty(productInfoVOList)){
            return true;
        }
        List<ProductCustomerDO> list = new ArrayList<>();
        for (ProductInfoVO productInfoVO : productInfoVOList) {
            ProductCustomerDO pcDo = new ProductCustomerDO();
            pcDo.setCustomerId(byId.getId());
            pcDo.setCustomerCode(byId.getCustomerCode());
            pcDo.setProductId(productInfoVO.getPrId());
            pcDo.setProductCode(productInfoVO.getPrCode());
            list.add(pcDo);
        }

        return  this.saveBatch(list);
    }



}
